import Component from '@teld/q-components/Uploader';
import { useQuasar } from '@teld/q-components';
import Card from '../card/Component';
import TList from '../list/List';
import TItem from '../item/Item';
import TIcon from '../icon/Component';
import TItemSection from '../item-section/ItemSection';
import TItemLabel from '../item-label/ItemLabel';
import TButton from 't/basic/button';
import TImg from '../img/Component.vue';
import TLinearProgress from '../linear-progress/Component';
import TUploaderAddTrigger from './UploaderAddTrigger';
import useMappingProps from 't/common/hooks/useMappingProps';
import {
  commonProps,
  fixNameSpace,
  pickOwnForBasicComponent,
} from 't/common/utils';
import { defineComponent, onMounted, ref, computed, watch } from 'vue';
import styles from './index.module.scss';
import './index.scss';
import { console } from 't/third-party/vuedraggable/util/console';
import label from '../label';
import { debounceFilter } from '@vueuse/core';
import uploaderImage from 'components/basic/uploader/upload.png';
import UndoRedoVue from 'src/views/mutation/UndoRedo.vue';

export * from '@teld/q-components/Uploader';

export default defineComponent({
  name: fixNameSpace(Component.name),
  directives: {
    removeTabindex: {
      mounted(el) {
        // 移除 tabindex 属性
        el?.removeAttribute('tabindex');
      },
    },
  },
  props: {
    ...commonProps,
    ...Component.props,
    multiple: {
      type: Boolean,
      default() {
        return false;
      },
    },
    otherRules: {
      type: String,
      default() {
        return '';
      },
    },
    maxFileSize: {
      type: [String, Number],
      default: null,
    },
    uploaderUrlType: {
      type: String,
      default() {
        return 'system';
      },
    },
    color: {
      type: String,
      default() {
        return '#FFFFFF';
      },
    },
    headers: {
      type: Array,
      default() {
        return [];
      },
    },
  },
  emits: [
    'update:show',
    'uploaded',
    'uploading',
    'failed',
    'rejected',
    'added',
    'removed',
    'factory-failed',
  ],

  setup(props, { attrs, emit, expose, slots }) {
    const refComponent = ref();
    const $q = useQuasar();
    const fileIconColorMap = {
      // 添加更多文件类型和对应的图标及颜色
      jpg: { icon: 'icon-t-pic', color: '#ff7b85' },
      png: { icon: 'icon-t-pic', color: '#ff7b85' },
      jpeg: { icon: 'icon-t-pic', color: '#ff7b85' },
      ico: { icon: 'icon-t-pic', color: '#ff7b85' },
      doc: { icon: 'icon-t-file-word', color: '#2394ff' },
      docx: { icon: 'icon-t-file-word', color: '#2394ff' },
      xls: { icon: 'icon-t-file-excel', color: '#4dc238' },
      xlsx: { icon: 'icon-t-file-excel', color: '#4dc238' },
      ppt: { icon: 'icon-t-file-ppt', color: '#ff9540' },
      pptx: { icon: 'icon-t-file-ppt', color: '#ff9540' },
      pdf: { icon: 'icon-t-file-pdf', color: '#FF5A66' },
      txt: { icon: 'icon-t-file-text', color: '#59ccb2' },
      zip: { icon: 'icon-t-file-zip', color: '#ffd76a' },
      rar: { icon: 'icon-t-file-zip', color: '#ffd76a' },
    };
    const [mappingProps, mappingExpose] = useMappingProps(props, {
      checkFileType(file) {
        // 从文件名中提取文件扩展名
        const extension = file.name.split('.').pop();
        // 使用文件扩展名从字典中获取对应的图标和颜色
        return (
          fileIconColorMap[extension] || {
            icon: 'icon-t-file-unknown',
            color: '#d9d9d9',
          }
        );
      },
      pickAndAddFiles() {
        if (refComponent.value) {
          // 调用上传方法
          refComponent.value.addFiles();
        }
      },
      pickFiles() {
        refComponent.value.pickFiles(...arguments);
      },
      upload() {
        refComponent.value.upload(...arguments);
      },
      abort() {
        refComponent.value.abort(...arguments);
      },
      reset() {
        refComponent.value.reset(...arguments);
      },
      removeUploadedFiles() {
        refComponent.value.removeUploadedFiles(...arguments);
      },
      removeQueuedFiles() {
        refComponent.value.removeQueuedFiles(...arguments);
      },
      removeFile() {
        refComponent.value.removeFile(...arguments);
      },
      factoryFn(files) {
        const file = files[0];
        let fileType = file.type;
        let filenamearr = file.name.split('.');
        // 重命名增加时间戳
        const newName = file.newName;
        const customName = file.newCustomName;
        if (mappingProps.uploaderUrlType == 'system') {
          return {
            url:
              window.TeldWebConfig.ResourceURL +
              (fileType.startsWith('image/')
                ? '/api/resource/UploadImgByMultipart'
                : '/api/resource/UploadDocByMultipart'),
            method: 'POST',
            headers: [
              { name: 'Accept', value: '*/*' },
              { name: 'X-Token', value: readCookie('telda') },
              { name: 'SRC', value: 'Resource' },
            ],
            fieldName: newName,
            formFields: [
              {
                // name: file.name,
                name: newName,
                value: JSON.stringify({
                  // Name: file.name,
                  Name: newName,
                  Extension: filenamearr[filenamearr.length - 1],
                  pathid: '101',
                  // CustomFileName: filenamearr[0],
                  CustomFileName: customName,
                }),
              },
            ],
            batch: true,
            sendRow: true,
          };
        } else {
          let url = mappingProps.url ? mappingProps.url : null;
          return {
            url: url,
            method: 'POST',
            headers: mappingProps.headers,
            fieldName: newName,
          };
        }
      },
      files: computed(() => refComponent.value.files),
      queuedFiles: computed(() => refComponent.value.queuedFiles),
      uploadedFiles: computed(() => refComponent.value.uploadedFiles),
      uploadedSize: computed(() => refComponent.value.uploadedSize),
      uploadSizeLabel: computed(() => refComponent.value.uploadSizeLabel),
      uploadProgressLabel: computed(
        () => refComponent.value.uploadProgressLabel,
      ),
      canAddFiles: computed(() => refComponent.value.canAddFiles),
      canUpload: computed(() => refComponent.value.canUpload),
      isBusy: computed(() => refComponent.value.isBusy),
      isUploading: computed(() => refComponent.value.isUploading),
    });
    const convertToBytesWithUnit = sizeStr => {
      const units = {
        B: 1,
        KB: 1024,
        MB: 1024 * 1024,
        GB: 1024 * 1024 * 1024,
      };

      // 正则表达式匹配数字和单位
      const match = sizeStr.match(/^(\d+(?:\.\d+)?)\s*(B|KB|MB|GB)$/i);
      if (!match) {
        return null;
      }

      const value = parseFloat(match[1]);
      const unit = match[2].toUpperCase();
      return units[unit] ? value * units[unit] : null;
    };

    // 使用计算属性处理maxFileSize的单位转换
    let maxFileSize = computed(() => {
      if (mappingProps.maxFileSize) {
        // 调用转换函数并返回转换后的字节数
        const sizeStr = mappingProps.maxFileSize;
        return convertToBytesWithUnit(sizeStr);
      } else {
        // 如果没有设置maxFileSize，则返回默认值或null
        return undefined;
      }
    });
    expose(mappingExpose, maxFileSize);

    onMounted(() => {});
    function readCookie(n) {
      for (
        var t, r = n + '=', u = document.cookie.split(';'), i = 0;
        i < u.length;
        i++
      ) {
        for (t = u[i]; t.charAt(0) == ' '; ) t = t.substring(1, t.length);
        if (t.indexOf(r) == 0) return t.substring(r.length, t.length);
      }
      return null;
    }
    function onHide(params) {
      emit('update:show', params);
    }
    function uploading(params) {
      emit('uploading', params);
    }
    function uploaded(params) {
      const response = params.xhr.response;
      const files = params.files;
      var obj = JSON.parse(response);
      var code = obj.Code;
      var RelativeUrls = obj.RelativeUrls;
      for (var i = 0; i < files.length; i++) {
        // 获取当前对象的__progressLabel属性
        var filesProgress = files[i].__progressLabel;
        // console.log(filesProgress); // 输出每个对象的__status属性值
      }

      // console.log(code);
      if (code == '001') {
        Funcs.Notify(
          $q.lang.uploader.warning,
          $q.lang.uploader?.invalid || '上传失败，上传内容无效',
          'warning',
        );
      } else if (code == '002') {
        Funcs.Notify(
          $q.lang.uploader.warning,
          $q.lang.uploader?.Extension ||
            '上传失败，不支持的资源类型（后缀名）或PathId格式错误',
          'warning',
        );
      } else if (code == '003') {
        Funcs.Notify(
          $q.lang.uploader.warning,
          $q.lang.uploader?.unknown ||
            '上传失败, 请检查文件名称是否包含_、+、&、%、斜杠等特殊字符，或未知的文件后缀',
          'warning',
        );
        mappingExpose.removeFile(files[0]);
      } else if (code == '004') {
        Funcs.Notify(
          $q.lang.uploader.warning,
          $q.lang.uploader?.maxLength ||
            '上传失败，文件名超出最大长度或文件名包含不支持的字符（_、+、&、%、斜杠等）',
          'warning',
        );
      } else {
        Funcs.Notify(
          $q.lang.uploader.warning,
          $q.lang.uploader?.success || '上传成功',
          'success',
        );
      }
      params.relativeUrls = RelativeUrls;
      emit('uploaded', params);
    }
    function failed(params) {
      Funcs.Notify(
        $q.lang.uploader.warning,
        $q.lang.uploader?.Extension ||
          '上传失败，不支持的资源类型（后缀名）或PathId格式错误',
        'warning',
      );
      emit('failed', params);
    }
    function rejected(params) {
      debugger;
      params.forEach(param => {
        // 遍历传入的数组
        let message = ''; // 初始化消息变量
        if (param.failedPropValidation === 'max-file-size') {
          message =
            $q.lang.uploader?.noFileSize || '文件大小不符合要求，请筛选后重试';
        } else if (param.failedPropValidation === 'accept') {
          message =
            $q.lang.uploader?.noFileType || '文件大小不符合要求，请筛选后重试';
        } else if (param.failedPropValidation === 'duplicate') {
          message = $q.lang.uploader?.duplicate || '请勿重复上传相同文件';
        } else {
          message = $q.lang.uploader?.maximum || '请勿超出最大上传数量';
        }
        Funcs.Notify($q.lang.uploader.warning, message, 'warning');
      });
      emit('rejected', params);
    }
    function makeTimeStringFlag() {
      const now = new Date();
      const year = now.getFullYear();
      const month = String(now.getMonth() + 1).padStart(2, '0'); // 月份从0开始，需要加1
      const day = String(now.getDate()).padStart(2, '0');
      const hours = String(now.getHours()).padStart(2, '0');
      const minutes = String(now.getMinutes()).padStart(2, '0');
      const seconds = String(now.getSeconds()).padStart(2, '0');
      const milliseconds = String(now.getMilliseconds()).padStart(3, '0');
      const formattedTimestamp = `${hours}${minutes}${seconds}`;
      return formattedTimestamp;
    }
    function added(params) {
      const files = params;
      // 定义特殊字符的正则表达式
      // const specialChars = /[_%&+\[\]\/?~]/;

      // 遍历所有添加的文件
      for (let i = 0; i < files.length; i++) {
        let filenamearr = files[i].name.split('.');
        // 重命名增加时间戳
        const extension = filenamearr.pop();
        const baseName = filenamearr.join('.');
        const timestamp = makeTimeStringFlag();
        const newName = `${baseName.replace(/[_%&+\[\]\/\\?~]/g, '-')}${timestamp}.${extension}`;
        files[i].newName = newName;
        files[i].newCustomName = `${baseName.replace(/[_%&+\[\]\/\\?~]/g, '-')}${timestamp}`;
        // 如果文件名包含特殊字符
        // if (specialChars.test(files[i].name)) {
        //   // 使用 Quasar Notify 插件显示提示信息
        //   Funcs.Notify(
        //     $q.lang.uploader.warning,
        //     $q.lang.uploader.checkFileName ||
        //       '上传失败，请检查文件名称是否包含_、+、&、%、斜杠等特殊字符',
        //     'warning',
        //   );

        //   // 从上传队列中移除包含特殊字符的文件
        //   //this.$refs.uploader.removeUploadedFile(files[i]);
        //   mappingExpose.removeFile(files[i]);
        //   // 也可以选择阻止上传过程
        //   //this.$refs.uploader.abort(); // 如果你想要取消上传过程
        //   return; // 结束函数执行
        // }
      }
      emit('added', params);
    }
    function removed(params) {
      emit('removed', params);
    }
    function start(params) {
      emit('start', params);
    }
    function finish(params) {
      emit('finish', params);
    }
    function factoryFailed(params) {
      emit('factory-failed', params);
    }
    function onClickHandler() {
      if (refComponent.value) {
        // 调用上传方法
        refComponent.value.upload();
      }
    }

    return () => {
      return (
        <div class={'t-uploader-all'} v-removeTabindex>
          <Component
            ref={refComponent}
            {...attrs}
            onUploading={uploading}
            onUploaded={uploaded}
            onFailed={failed}
            onRejected={rejected}
            onAdded={added}
            onRemoved={removed}
            tabIndex={'-1'}
            onStart={start}
            onFinish={finish}
            onFactoryFailed={factoryFailed}
            multiple={mappingProps.multiple}
            uploaderUrlType={mappingProps.uploaderUrlType}
            {...pickOwnForBasicComponent(mappingProps, Component.props, attrs)}
            class={['t-uploader', styles.module]}
            maxFileSize={maxFileSize.value}
            flat
            color={mappingProps.color}
            v-show={mappingProps.visible}
            factory={mappingExpose.factoryFn}
            // v-slots={{ ...slots }}
          >
            {{
              header(scope) {
                return (
                  <div>
                    <div class='uploader__background'>
                      <i class='q-icon notranslate material-icons'>
                        <img src={uploaderImage} alt='' />
                      </i>
                      <div class='upload__labels'>
                        {$q.platform.is.desktop && (
                          <span class='upload-label'>
                            {$q.lang.uploader?.tips || '将文件拖拽至此区域, 或'}
                          </span>
                        )}

                        <t-button
                          class='upload-clickable tr-button-text'
                          label={$q.lang.uploader?.add || '点击添加'}
                          tabIndex='1'
                          readonly={mappingProps.readonly||(!mappingProps.multiple&&scope.files.length>0)}
                          disable={
                            mappingProps.readonly || mappingProps.disable
                          }
                          onClick={() => {
                            const pointerType = event?.pointerType;
                            if (!pointerType && !$q.platform.is.mobile) {
                              scope.pickFiles();
                            }
                          }}
                        >
                          {!(mappingProps.readonly|| (!mappingProps.multiple&&scope.files.length>0))&& (
                            <TUploaderAddTrigger></TUploaderAddTrigger>
                          )}
                        </t-button>
                      </div>
                      <div class='upload-typerules'>
                        {mappingProps.accept && (
                          <span class='upload-typelabel'>
                            {$q.lang.uploader?.filesType || '文件支持的格式有'}
                            {mappingProps.accept}
                          </span>
                        )}
                        {mappingProps.accept && mappingProps.maxFileSize && (
                          <span class='upload-separator'>，</span>
                        )}
                        {mappingProps.maxFileSize && (
                          <span class='upload-maxfile'>
                            {$q.lang.uploader?.SingleFileSize ||
                              '单个文件大小请勿超过'}
                            {mappingProps.maxFileSize}
                          </span>
                        )}
                      </div>
                    </div>
                    {scope.files.length > 0 && (
                      <t-item flat class='upload-list'>
                        <t-item-section class='upload-list-title'>
                          {$q.lang.uploader?.uploadList || '上传文件列表'}
                        </t-item-section>
                        {!mappingProps.autoUpload && (
                          <t-item-section top side>
                            <t-button
                              size='14px'
                              flat
                              dense
                              tabIndex='1'
                              label={$q.lang.uploader?.start || '开始上传'}
                              color='#2394ff'
                              title='开始上传'
                              class='tr-button-text'
                              readonly={mappingProps.readonly}
                              disable={
                                mappingProps.readonly || mappingProps.disable
                              }
                              icon='icon-t-cloud-upload'
                              onClick={() => scope.upload()}
                            ></t-button>
                          </t-item-section>
                        )}

                        <t-item-section top side>
                          <t-button
                            size='14px'
                            flat
                            dense
                            tabIndex='1'
                            title={
                              $q.lang.uploader?.deleteUploadList ||
                              '删除上传文件列表'
                            }
                            color='#ff5a66'
                            class='tr-button-icon-text'
                            readonly={mappingProps.readonly}
                            disable={
                              mappingProps.readonly || mappingProps.disable
                            }
                            icon='icon-t-delete-outlined'
                            onClick={() => scope.removeUploadedFiles()}
                          ></t-button>
                        </t-item-section>
                      </t-item>
                    )}
                  </div>
                );
              },

              list(scope) {
                console.log(scope);
                return (
                  <t-list class='uploadfiles-list'>
                    {scope.files.length === 0 && (
                      <div>
                        {(mappingProps.otherRules ||
                          mappingProps.maxFileSize) && (
                          <div style='padding-bottom:6px'>
                            <span class='upload-rules'>
                              {$q.lang.uploader?.rules || '上传规则'}
                            </span>
                          </div>
                        )}
                        <div class='upload-ruleslist'>
                          {mappingProps.maxFileSize && (
                            <span class='upload-maxfilesize'>
                              {$q.lang.uploader?.maxSize || '文件大小请勿超过'}
                              {mappingProps.maxFileSize}
                            </span>
                          )}
                          {mappingProps.otherRules && (
                            <span class='upload-other-rules'>
                              {mappingProps.otherRules}
                            </span>
                          )}
                        </div>
                      </div>
                    )}
                    {scope.files.map(file => (
                      <t-item key={file.__key} noborder>
                        {/* {JSON.stringify(file)} */}
                        <t-item-section top side class='upload-list-icon'>
                          <t-icon
                            size='14px'
                            name={mappingExpose.checkFileType(file).icon}
                            color={mappingExpose.checkFileType(file).color}
                          ></t-icon>
                        </t-item-section>
                        <t-item-section>
                          <t-item-label className='full-width ellipsis upload-filename'>
                            {file.newName}
                          </t-item-label>
                          <t-item-label caption>
                            {file.__sizeLabel} / {file.__progressLabel}
                          </t-item-label>
                          {file.__status !== 'uploaded' && (
                            <t-linear-progress
                              size='3px'
                              trackColor='#F0F2F5'
                              value={file.__progressLabel}
                            />
                          )}
                        </t-item-section>
                        <t-item-section top side>
                          <t-button
                            size='14px'
                            flat
                            tabIndex='1'
                            dense
                            color='rgba(0,0,0,0.32)'
                            class='tr-button-icon-text'
                            readonly={mappingProps.readonly}
                            disable={
                              mappingProps.readonly || mappingProps.disable
                            }
                            icon='fas dx-icon icon-t-close-circle'
                            onClick={() => scope.removeFile(file)}
                          ></t-button>
                        </t-item-section>
                      </t-item>
                    ))}
                  </t-list>
                );
              },
            }}
          </Component>
        </div>
      );
    };
  },
});
